import 'dart:convert';

import 'complex_data.dart';

/// A codec that can serialize both [ComplexData1] and [ComplexData2].
class ExtraCodec extends Codec<Object?, Object?> {
  /// Create a codec.
  const ExtraCodec();

  @override
  Converter<Object?, Object?> get decoder => const _ExtraDecoder();

  @override
  Converter<Object?, Object?> get encoder => const _ExtraEncoder();
}

class _ExtraDecoder extends Converter<Object?, Object?> {
  const _ExtraDecoder();

  @override
  Object? convert(Object? input) {
    if (input == null) {
      return null;
    }
    final List<Object?> inputAsList = input as List<Object?>;
    switch (inputAsList[0]) {
      case 'ComplexData':
        return ComplexData(inputAsList[1]! as String);
      default:
        throw FormatException('Unable tp parse input: $input');
    }
  }
}

class _ExtraEncoder extends Converter<Object?, Object?> {
  const _ExtraEncoder();

  @override
  Object? convert(Object? input) {
    if (input == null) {
      return null;
    }
    switch (input.runtimeType) {
      case ComplexData:
        return <Object?>['ComplexData', (input as ComplexData).data];
      default:
        throw FormatException('Cannot encode type ${input.runtimeType}');
    }
  }
}
